messages is package{
  -- implement message box in terms of tasks
  import concurrency;
  
  type mbox of %t is mbox{
    post has type (%t)=>task of %t;
    grab has type ()=> task of %t;
  }
  
  box() is mbox{
    private var Q := queue of {};
    
    private _ is background msgLoop();
   
    private grabMsgChnl is channel();
    private postMsgChnl is channel();
   
    post(M) is send(postMsgChnl,M);
    grab() is let{
      ReplyChnl is channel();
    } in wrapRv(sendRv(grabMsgChnl,ReplyChnl),(function(_) is recv(ReplyChnl)));
   
    private msgLoop() is task{
      while true do{
        select{
          on receive M on postMsgChnl do {
            Q := queue of {Q..;M}
          };
          when Q matches queue of {H;..QQ} on receive Reply on grabMsgChnl do {
            Q := QQ;
            send H to Reply
          }
        }
      }
    }
  }
}